<template>
  <div class="query-grid-main">
    <toolbar
      :importUrl="importUrl"
      :downloadUrl="downloadUrl"
      :queryClick="query"
      :newClick="newClick"
      :deleteClick="del"
      :deleteBtnDisabled="selection.length == 0"
      :downloadClick="downloadClick"
      :operating="toolbarOperating"
    />
    <div
      class="query-form-main"
      :style="
        exp && formHeight > 90
          ? { height: formHeight + 'px' }
          : { marginBottom: '5px' }
      "
    >
      <form-edit
        :form="queryForm"
        ref="form"
        :options="options"
        :columns="queryColumns"
        :showToolbar="false"
        size="small"
      />
    </div>
    <div class="query-form-exp" @click="exp = !exp" v-if="formHeight > 90">
      <span>{{ exp ? "收起" : "展开" }}</span>
      <i :class="exp ? 'el-icon-arrow-up' : 'el-icon-arrow-down'" />
    </div>
    <grid
      ref="grid"
      :tableName="tableName"
      :sysName="sysName"
      :columns="columns"
      :rowKey="rowKey"
      :height="height"
      :queryParams="queryParams"
      :operating="gridOperating"
      :pageNo="pageNo"
      :pageSize="pageSize"
      :size="size"
      :sorts="sorts"
      :fixeds="fixeds"
      :multiple="multiple"
      :border="border"
      :editClick="editClick"
      :deleteClick="del"
      v-model="selection"
    />
  </div>
</template>

<script>
import Grid from "./Grid.vue";
import Toolbar from "@comp/base/Toolbar.vue";
import FormEdit from "@comp/form/FormEdit.vue";
export default {
  components: { Grid, Toolbar, FormEdit },
  props: {
    queryForm: Object,
    queryOptions: {
      type: Object,
      required: true,
      validator: function(obj) {
        for (let i = 0; i < Object.keys(obj).length; i++) {
          const key = Object.keys(obj)[i];
          if (typeof obj[key] != "string" && typeof obj[key] != "object") {
            console.error(
              `/src/pages/main/components/grid/QueryGrid.vue 组件属性queryOptions校验失败，${key}值的类型必须是String或Object`
            );
            return false;
          } else if (typeof obj[key] == "string") {
            return true;
          } else if (
            typeof obj[key] == "object" &&
            (!obj[key].hasOwnProperty("label") ||
              !obj[key].hasOwnProperty("type"))
          ) {
            console.error(
              `/src/pages/main/components/grid/QueryGrid.vue 组件属性queryOptions校验失败，在${key}属性中必须包含label、type`
            );
            return false;
            break;
          }
        }
        return true;
      },
    },
    queryColumns: {
      type: Number,
      default: 1,
      validator: (value) => value <= 4,
    },
    tableName:{type:String},
    sysName:{type:String},
    importUrl: String,
    downloadUrl: String,
    size: {
      type: String,
      validator: function(value) {
        return (
          ["medium", "small", "mini"].findIndex((item) => item == value) >= 0
        );
      },
      default: "medium",
    },
    border: { type: Boolean, default: false },
    rowKey: { type: String, required: true },
    multiple: { type: Boolean, default: false },
    sorts: {
      type: [Array, String],
      default: () => "no",
      validator: function(value) {
        return (
          ["all", "no"].findIndex((item) => item == value) >= 0 ||
          Array.isArray(value)
        );
      },
    },
    pageSize: { type: Number, default: 20 },
    pageNo: { type: Number, default: 1 },
    height: Number,
    fixeds: { type: Array, default: () => [] },
    operating: {
      type: [Array, Boolean],
      validator: function(arr) {
        const list = [
          "edit",
          "delete",
          "new",
          "download",
          "import",
          "query",
          "info",
          "save",
        ];
        for (let i = 0; i < arr.length; i++) {
          if (list.findIndex((item) => item == arr[i]) < 0) {
            console.error(
              '/src/pages/main/components/grid/Grid.vue 属性检查失败，属性operating的值只能是false或数组["edit", "delete", "new", "download", "import","query","info","save"]'
            );
            return false;
          }
        }
        if (arr == true) {
          console.error(
            '/src/pages/main/components/grid/Grid.vue Grid.vue属性检查失败，属性operating的值只能是false或数组["edit", "delete", "new", "download", "import","query","info","save"]'
          );
          return false;
        }
        return true;
      },
      default: () => ["edit", "delete", "new", "query", "info"],
    },
    editClick: {
      type: Function,
      default: (index, row) => {
        console.log(index, row);
      },
    },
    deleteClick: {
      type: Function,
    },
    newClick: {
      type: Function,
      default: () => {
        console.log("new button click");
      },
    },
    downloadClick: {
      type: Function,
    },
    queryClick: {
      type: Function,
    },
    columns: {
      type: Array,
      required: true,
      validator: function(item) {
        for (let i = 0; i < item.length; i++) {
          if (!item[i].hasOwnProperty("label")) {
            console.error(
              "/src/pages/main/components/grid/Grid.vue Grid.vue属性检查失败，表格组件的列（columns）属性缺失(label)属性值!",
              item[i]
            );
            return false;
          }
          if (!item[i].hasOwnProperty("prop")) {
            console.error(
              "/src/pages/main/components/grid/Grid.vue Grid.vue属性检查失败，表格组件的列（columns）属性缺失(prop)属性值!",
              item[i]
            );
            return false;
          }
        }
        return true;
      },
    },
  },
  data() {
    return {
      queryParams: this.queryForm,
      selection: [],
      // options: {},
      exp: false,
      formHeight: 80,
    };
  },
  computed: {
    toolbarOperating() {
      if (typeof this.operating != "undefined") {
        if (!this.multiple) {
          if (Array.isArray(this.operating)) {
            return this.operating.filter(
              (item) =>
                ["new", "query", "import", "download", "save"].indexOf(item) >=
                0
            );
          }
          return false;
        } else {
          if (Array.isArray(this.operating)) {
            return this.operating.filter(
              (item) =>
                [
                  "new",
                  "query",
                  "delete",
                  "import",
                  "download",
                  "save",
                ].indexOf(item) >= 0
            );
          }
          return false;
        }
      }
      return false;
    },
    //匹配grid的按钮组合
    gridOperating() {
      if (typeof this.operating != "undefined") {
        if (this.multiple) {
          if (Array.isArray(this.operating)) {
            return this.operating.filter(
              (item) => ["edit", "info"].indexOf(item) >= 0
            );
          }
          return false;
        } else {
          if (Array.isArray(this.operating)) {
            return this.operating.filter(
              (item) => ["edit", "delete", "info"].indexOf(item) >= 0
            );
          }
        }
      }
      return false;
    },
    options() {
      const keys = Object.keys(this.queryOptions);
      const opts = {};
      for (let i = 0; i < keys.length; i++) {
        //先获取columns中对应的column，之后在用来匹配dictName等
        const col = this.columns.find((item) => {
          if (item.prop == keys[i]) {
            return item;
          }
        });
        const opt = this.queryOptions[keys[i]];
        const optObj = {};
        if (typeof col != "undefined") {
          if (typeof opt == "string") {
            if (["check", "radio", "select", "cascader"].indexOf(opt) > -1) {
              //字典类的组件，需要增加字典名称属性
              optObj = {
                type: opt,
                label: col.label,
                dictName: col.dictName,
              };
            } else if (opt == "auto") {
              optObj = {
                type: opt,
                lable: col.label,
                autoUrl: col.autoUrl,
                autoParams: col.autoParams,
              };
            } else if (
              ["time", "date", "datetime", "year", "month", "week"].indexOf(
                opt
              ) > -1
            ) {
              optObj = {
                type: opt,
                label: col.label,
                format: col.format,
                range: true,
              };
            } else {
              optObj = { type: opt, label: col.label };
            }
          } else {
            if (
              ["check", "radio", "select", "cascader"].indexOf(opt.type) > -1
            ) {
              //字典类的组件，需要增加字典名称属性
              optObj = { ...opt, dictName: col.dictName };
            } else if (opt == "auto") {
              optObj = {
                ...opt,
                autoUrl: col.autoUrl,
                autoParams: col.autoParams,
              };
            } else if (
              ["time", "date", "datetime", "year", "month", "week"].indexOf(
                opt.type
              ) > -1
            ) {
              optObj = { ...opt, format: col.format, range: true };
            } else {
              optObj = { ...opt };
            }
          }
        } else {
          optObj = { ...opt };
        }
        opts[keys[i]] = optObj;
      }
      return opts;
    },
  },
  methods: {
    dc() {
      console.log("down");
    },
    query() {
      if (typeof this.queryClick != "undefined") {
        this.queryClick(this.selection);
      } else {
        if (typeof this.$refs.grid != "undefined") {
          this.$refs.grid.load(this.queryParams);
        }
      }
    },
    del(row) {
      if (typeof this.deleteClick != "undefined") {
        this.deleteClick(this.selection);
      } else {
        if (typeof this.$refs.grid != "undefined") {
          this.$refs.grid.del(row);
        }
      }
    },
  },
  mounted() {
    /**
     * 记录form的实际高度
     */
    this.formHeight =
      (Object.keys(this.queryOptions).length / this.queryColumns) * 40 + 10;
  },
};
</script>

<style lang="less">
.query-form-main {
  margin-top: 5px;
  background-color: #f2f2f2;
  padding: 10px;
  overflow: hidden;
}
.query-form-exp {
  border-top: 1px solid #e0e0e0;
  background-color: #f2f2f2;
  padding: 3px;
  text-align: center;
  margin-bottom: 5px;
  font-size: 14px;
  cursor: pointer;
}
.el-form-item {
  margin-bottom: 5px !important;
}
</style>
